#include "GroupItem.h"

#include <stdio.h>
#include <stdlib.h>

struct _GroupItemPriv
{
	EventHash   *member_list;
	EventString *group_name;
};

static void
group_item_finalize(GroupItem *self)
{
	event_object_unref(self->priv->group_name);
	event_object_unref(self->priv->member_list);
	free(self->priv);
}

GroupItem *
group_item_new(void)
{
	GroupItem     *object = MALLOC_NEW(GroupItem);
	GroupItemPriv *priv   = MALLOC_NEW(GroupItemPriv);

	event_object_init(EVENT_OBJECT(object));
	event_object_set_finalize(object, FINALIZE(group_item_finalize));
	//
	object->create_date = 0;
	object->modify_date = 0;
	object->group_id    = 0;
	object->user_id	    = 0;
	object->g_can_write = false;
	object->can_join    = false;
	object->priv	    = priv;
	//
	priv->member_list = event_hash_new(EVENT_HASH_MODEL_NUMBER);
	priv->group_name  = NULL;

	return object;
}

const EventString *
group_item_get_group_name(GroupItem *self)
{
	return_val_if_fail(self != NULL, group_item_get_group_name, NULL);
	return self->priv->group_name;
}

EventString *
group_item_dup_group_name(GroupItem *self)
{
	return_val_if_fail(self != NULL, group_item_get_group_name, NULL);
	return EO_REF(self->priv->group_name, EventString);
}

void
group_item_set_group_name(GroupItem *self, EventString *group_name)
{
	return_if_fail(self != NULL || group_name != NULL,
		       group_item_set_group_name);
	event_object_unref(self->priv->group_name);
	self->priv->group_name = EO_REF(group_name, EventString);
}

void
group_item_iter_member_reset(GroupItem *self)
{
	return_if_fail(self != NULL, group_item_iter_member_reset);
	event_hash_iter_reset(self->priv->member_list);
}

GMember *
group_item_iter_get_with_member(GroupItem *self)
{
	static GMember g_member;
	HashItem_p     h_item;

	return_val_if_fail(self != NULL, group_item_iter_get_with_member, NULL);

	h_item = event_hash_iter_get(self->priv->member_list);
	if (!h_item)
		return NULL;
	g_member.user_id   = (euint32)(euint64)event_hash_item_get_key(h_item);
	g_member.can_write = (bool)(euint64)event_hash_item_get_value(h_item);
	return &g_member;
}

void
group_item_set_member(GroupItem *self, euint32 user_id, bool can_write)
{
	return_if_fail(self != NULL, group_item_set_member);
	event_hash_set(self->priv->member_list, EPTR((euint64)user_id),
		       EPTR((euint64)can_write), NULL);
}

int
group_item_remove_member(GroupItem *g_item, euint32 user_id)
{
	return_val_if_fail(g_item != NULL, group_item_remove_member, 2);
	if (!event_hash_verify_exist(g_item->priv->member_list,
				     EPTR((euint64)user_id))) {
		return 1;
	}
	event_hash_remove(g_item->priv->member_list, EPTR((euint64)user_id));
	return 0;
}

bool
group_item_verify_write_flag(GroupItem *self, euint32 user_id)
{
	return_val_if_fail(self != NULL, group_item_verify_write_flag, false);
	return (bool)(euint64)event_hash_get(self->priv->member_list,
					     EPTR((euint64)user_id));
}

bool
group_item_verify_user_existed(GroupItem *self, euint32 user_id)
{
	return_val_if_fail(self != NULL, group_item_verify_write_flag, false);
	return event_hash_verify_exist(self->priv->member_list,
				       EPTR((euint64)user_id));
}

void
__group_item_print_hash_status(GroupItem *self)
{
	return_if_fail(self != NULL, __group_item_print_hash_status);

	event_hash_print_status(self->priv->member_list);
}
